import numpy as np
import csv
import random
from datetime import datetime
from time import strftime
import pysal as pysal

'''
test max_p in pysal with synthetic cancer data
'''

def getCurTime():
    """
    get current time
    Return value of the date string format(%Y-%m-%d %H:%M:%S)
    """
    format='%Y-%m-%d %H:%M:%S'
    sdate = None
    cdate = datetime.now()
    try:
        sdate = cdate.strftime(format)
    except:
        raise ValueError
    return sdate

def build_data_list():
    #print getCurTime()
    sKey = np.array([])
    fn = unitCSV    # input csv location
    ra = csv.DictReader(file(fn), dialect="excel")
    
    for record in ra:
        temp = np.array([])
        for i in range(1,1002):
            temp = np.append(temp, int(float(record[ra.fieldnames[i]])))
        #temp = [int(float(record["ID"])), int(float(record[cancerFN])), int(float(record[popFN])), float(record[cancerFN])/float(record[popFN]), 0.0]
        sKey = np.append(sKey, temp)

    sKey.shape = (1000,-1)
    #print sKey[:,1]
    #print getCurTime()
    #print sKey
    return sKey

def calOriRate(unit_cancer, unit_pop):
    sKey = np.array([])
    i = 0
    for item in unit_cancer:
        sKey = np.append(sKey, float(unit_cancer[i]/unit_pop[i]))
        i += 1
    sKey.shape = (-1,1)
    return sKey

def build_smooth_list(inputCSV):
    fn = inputCSV
    ra = csv.DictReader(file(fn), dialect="excel")
    temp_smoothed_rate = np.array([])

    for record in ra:
        #print record[ra.fieldnames[0]], type(record[ra.fieldnames[-1]])
        #unit_attri[i,4] = int(float(record[ra.fieldnames[-1]]))
        temp_smoothed_rate = np.append(temp_smoothed_rate, float(record["SmoothedRate"]))
    temp_smoothed_rate.shape = (-1,1)
    return temp_smoothed_rate


def dictolist(temp_dict):
    region = np.array([])
    for k, v in temp_dict.iteritems():
        region = np.append(region, [int(k), v])
    region.shape = (-1, 2)
    region = region[np.argsort(region[:,0]),:]
    return region
    
        
#--------------------------------------------------------------------------
#MAIN

if __name__ == "__main__":
    #inputs = get_inputs()
    print "begin at " + getCurTime()

    high_rate = "15"
    #unitCSV = "C:/_DATA/CancerData/test/Mar21/cancer1000_"+high_rate+".csv"
    unitCSV = "C:/_DATA/CancerData/test/Jan15/TP1000_1m.csv"
    popFN = "pop"
    
    #filePath = "C:/_DATA/CancerData/test/Jan15/Thousand/10000/OO_CLK/"
    #filePath = "F:/OO_WARD/"
    dataMatrix = build_data_list()  # [pop, cancer1, cancer2, cancer3]
    unit_pop = dataMatrix[:,0]
    unit_pop.shape = (-1,1)
    w = pysal.rook_from_shapefile("C:/_DATA/CancerData/test/Jan15/TP1000_1m.shp")

    j = 0
    while j < 1:
        if j == 0:
            soMethod = "OO"
        elif j == 1:
            soMethod = "SO"
        elif j == 2:
            soMethod = "SS"
        else:
            print "error!"
            break

        filePath = "C:/_DATA/CancerData/test/Mar21/"+high_rate+"/"
        
        repeat = 179
        smoothed_region_10000 = np.arange(1000)
        smoothed_region_8000 = np.arange(1000)
            
        #while repeat < 1001:
        while repeat < 180:
            #regionCSV = filePath + soMethod +"_WARD_10000_cancer"+ str(repeat) +".csv"
            regionCSV = "C:/_DATA/CancerData/test/Jan15/Thousand/10000/cancer179/maps/cancer179_CLK_OO.csv"
            sField_Ob = "cancer" + str(repeat)
            #unit_attri = build_unit_list(sField_Ob) # [FID, cancer, pop, cancer/pop, smoothed_rate]

            unit_cancer = dataMatrix[:,repeat]
            unit_cancer.shape = (-1,1)

            original_rate = calOriRate(unit_cancer, unit_pop)
            smoothed_rate = build_smooth_list(regionCSV)

            pvalue_path = "C:/_DATA/CancerData/test/Jan15/Thousand/10000/cancer179/"

            # for original rate            
            region_original = pysal.Maxp(w,original_rate,floor=10000,floor_variable=unit_pop,initial=99)
            #np.savetxt("C:/_DATA/CancerData/test/Mar21/pvalue/15/"+ sField_Ob +"_maxp_OO_10000.csv", dictolist(region_original.area2region), delimiter=',')
            np.savetxt(pvalue_path + sField_Ob +"_maxp_OO_10000.csv", dictolist(region_original.area2region), delimiter=',')
  
            # for smoothed rate            
            region_smoothed = pysal.Maxp(w,smoothed_rate,floor=10000,floor_variable=unit_pop,initial=99)
            np.savetxt(pvalue_path + sField_Ob+"_maxp_SS_10000.csv", dictolist(region_smoothed.area2region), delimiter=',')                   
            repeat = repeat + 1
        j = j + 1
    print "end at " + getCurTime()
    print "========================================================================"  

    """
    pysal.region.maxp.Maxp 
    
    Parameters
    ----------
 
    w               : W
                      spatial weights object
                    
    z               : array
                      n*m array of observations on m attributes across n
                      areas. This is used to calculate intra-regional
                      homogeneity
    floor           : int
                      a minimum bound for a variable that has to be
                      obtained in each region
    floor_variable  : array
                      n*1 vector of observations on variable for the floor
    initial         : int 
                      number of initial solutions to generate
    verbose         : binary
                      if true debugging information is printed
    seeds           : list
                      ids of observations to form initial seeds. If
                      len(ids) is less than the number of observations, the
                      complementary ids are added to the end of seeds. Thus
                      the specified seeds get priority in the solution
     
    Attributes
    ----------

    area2region     : dict
                      mapping of areas to region. key is area id, value is
                      region id
    regions         : list
                      list of lists of regions (each list has the ids of areas
                      in that region)
    p               : int
                      number of regions
    swap_iterations : int
                      number of swap iterations
    total_moves     : int
                      number of moves into internal regions

    Examples
    --------

    Setup imports and set seeds for random number generators to insure the
    results are identical for each run.

    >>> import random
    >>> import numpy as np
    >>> import pysal
    >>> random.seed(100)
    >>> np.random.seed(100)
    
    Setup a spatial weights matrix describing the connectivity of a square
    community with 100 areas.  Generate two random data attributes for each area
    in the community (a 100x2 array) called z. p is the data vector used to
    compute the floor for a region, and floor is the floor value; in this case
    p is simply a vector of ones and the floor is set to three. This means
    that each region will contain at least three areas.  In other cases the
    floor may be computed based on a minimum population count for example.

    >>> w=pysal.lat2W(10,10)
    >>> z=np.random.random_sample((w.n,2))
    >>> p=np.ones((w.n,1),float)
    >>> floor=3
    >>> solution=pysal.region.Maxp(w,z,floor,floor_variable=p,initial=100)
    >>> solution.p
    29
    >>> solution.regions[0]
    [4, 14, 5, 24, 3]
    >>> 

    """


           
